<template>
  <section style="padding:10px;">
    <el-row :gutter="10">
      <el-col :span="6">
        <el-card>
          <template #header>
            <div class="clearfix">
              <span>角色</span>
              <el-button
                :loading="loadingRoles"
                type="text"
                style="float: right; padding: 3px 0"
                @click="getRoles"
              >刷新</el-button>
            </div>
          </template>
          <div
            v-for="o in roles"
            :key="o.id"
            :class="o.id == roleId ? 'active' : ''"
            class="item role-item"
            @click="roleSelect(o.id)"
          >
            <span>{{ o.name }}</span>
            <span style="float:right;">{{ o.description }}</span>
          </div>
        </el-card>
      </el-col>
      <el-col :span="18">
        <el-card>
          <template #header>
            <div class="clearfix">
              <span>平台权限</span>
              <my-confirm-button
                v-if="checkPermission(['admin_sysrolepermission_add'])"
                :validate="saveValidate"
                :loading="loadingSave"
                :disabled="disabledSave"
                :placement="'left'"
                type="text"
                class="save"
                style="float: right;"
                @click="save"
              >
                <template #content>
                  <p>确定要保存吗？</p>
                </template>
                保存
              </my-confirm-button>
              <el-button
                :loading="loadingPermissions"
                type="text"
                style="float: right; padding: 3px 0"
                @click="getPermissions"
              >刷新</el-button>
            </div>
          </template>

          <el-tabs v-model="activeName" type="card">
            <el-tab-pane label="Web权限" name="first">
              <el-table
                ref="multipleTable"
                :data="permissionTree"
                :default-expand-all="true"
                :tree-props="{ children: 'children', hasChildren: 'hasChildren' }"
                row-key="id"
                highlight-current-row
                style="width: 100%;"
                @select-all="onSelectAll"
                @select="onSelect"
              >
                <el-table-column type="selection" width="50" />
                <el-table-column prop="label" label="导航菜单" width="200" />
                <el-table-column label="菜单接口" width>
                  <template #default="{ row }">
                    <el-checkbox-group v-if="row.apis && row.apis.length > 0" v-model="chekedApis">
                      <el-checkbox v-for="api in row.apis" :key="api.id" :label="api.id" @change="(value)=>onChange(value, row.id)">{{ api.name }}</el-checkbox>
                    </el-checkbox-group>
                  </template>
                </el-table-column>
              </el-table>

            </el-tab-pane>
            <el-tab-pane label="App权限" name="second">

              <el-table
                ref="multipleTable2"

                :data="permissionTree2"
                :default-expand-all="true"
                :tree-props="{ children: 'children', hasChildren: 'hasChildren' }"
                row-key="id"
                highlight-current-row
                style="width: 100%;"
                @select="onSelect2"
                @select-all="onSelectAll2"
              >
                <el-table-column type="selection" width="50" />
                <el-table-column prop="label" label="APP接口" width="200">
                  <!-- <template #default="{ row }">
                    <el-checkbox :label="row.id" @change="(value)=>onSelect2(value, row)">{{ row.label }}</el-checkbox>
                  </template> -->
                </el-table-column>

              </el-table>

            </el-tab-pane>

          </el-tabs>

        </el-card>
      </el-col>
    </el-row>
  </section>
</template>

<script>
import { treeToList, listToTree, getTreeParentsWithSelf } from '@/utils'
import { getRoleListPage } from '@/api/admin/role'
import {
  getPermissions,
  getPermissionIds,
  addRolePermission
} from '@/api/admin/rolepermission'
import MyConfirmButton from '@/components/my-confirm-button'

export default {
  name: 'Assign',
  components: {
    MyConfirmButton
  },
  data() {
    return {
      roles: [],
      roleId: 0,
      table: false,
      activeName: 'first',
      permissionTree: [],
      permissionTree2: [],
      apis: [],
      loadingRoles: false,
      loadingPermissions: false,
      loadingSave: false,
      checkedPermissions: [],
      checkedPermissions2: [],
      chekedApis: [],
      checked: true
    }
  },
  computed: {
    disabledSave() {
      return !(
        this.roleId
      )
    }
  },
  mounted() {
    this.getRoles()
    this.getPermissions()
  },
  methods: {
    // 获取角色列表
    async getRoles() {
      this.loadingRoles = true
      const res = await getRoleListPage()
      this.loadingRoles = false
      this.roles = res.data?.rows
    },
    // 获取权限树
    async getPermissions() {
      this.table
      this.loadingPermissions = true
      this.onSelectAll([])
      this.onSelectAll2([])
      this.onSelect2(false, null)
      const para = {}
      const res = await getPermissions(para)
      this.loadingPermissions = false
      const tree = listToTree(_.cloneDeep(res.data.menus))
      const appApis = listToTree(_.cloneDeep(res.data.appapis))
      this.permissionTree = tree
      this.permissionTree2 = appApis
      this.getRolePermission()
    },
    // 获取角色权限
    async getRolePermission() {
      if (!this.roleId) {
        return
      }
      this.loadingPermissions = true
      const para = { roleId: this.roleId }
      const res = await getPermissionIds(para)

      this.loadingPermissions = false
      const permissionIds = res.data
      const rows = treeToList(this.permissionTree)
      const rows2 = treeToList(this.permissionTree2)
      rows.forEach(row => {
        const checked = permissionIds.includes(row.id)
        this.$refs.multipleTable.toggleRowSelection(row, checked)
      })
      // app权限
      rows2.forEach(row => {
        const checked = permissionIds.includes(row.id)
        this.$refs.multipleTable2.toggleRowSelection(row, checked)
      })

      this.checkedPermissions = this.$refs.multipleTable.selection.map(s => {
        return s.id
      })

      this.$refs.multipleTable2.selection.map(s => {
        this.checkedPermissions.push(s.id)
      })

      const apiIds = []
      permissionIds.forEach(permissionId => {
        if (!this.checkedPermissions.includes(permissionId)) {
          apiIds.push(permissionId)
        }
      })
      this.chekedApis = apiIds
    },
    // 验证保存
    saveValidate() {
      let isValid = true
      if (!this.roleId) {
        this.$message({
          message: '请选择角色！',
          type: 'warning'
        })
        isValid = false
        return isValid
      }
      // if (!(this.checkedPermissions.length > 0 || this.chekedApis.length > 0 || this.checkedPermissions2.length > 0)) {
      //   this.$message({
      //     message: '请选择权限！',
      //     type: 'warning'
      //   })
      //   isValid = false
      //   return isValid
      // }
      return isValid
    },
    // 保存权限
    async save() {
      const permissionIds = [...this.checkedPermissions]
      if (this.chekedApis.length > 0) {
        permissionIds.push(...this.chekedApis)
      }
      const para = { permissionIds, roleId: this.roleId }

      this.loadingSave = true
      const res = await addRolePermission(para)
      this.loadingSave = false

      if (!res?.success) {
        return
      }

      this.$message({
        message: this.$t('admin.saveOk'),
        type: 'success'
      })
    },
    roleSelect(id) {
      this.roleId = id
      this.onSelectAll([])
      this.onSelectAll2([])
      this.onSelect2(false, null)
      this.getRolePermission()
    },
    selectApis(checked, row) {
      if (row.apis) {
        row.apis.forEach(a => {
          const index = this.chekedApis.indexOf(a.id)
          if (checked) {
            if (index === -1) {
              this.chekedApis.push(a.id)
            }
          } else {
            if (index > -1) {
              this.chekedApis.splice(index, 1)
            }
          }
        })
      }
    },
    onSelectAll(selection) {
      const selections = treeToList(selection)
      const rows = treeToList(this.permissionTree)
      const checked = selections.length === rows.length
      rows.forEach(row => {
        this.$refs.multipleTable.toggleRowSelection(row, checked)
        this.selectApis(checked, row)
      })

      this.checkedPermissions = this.$refs.multipleTable.selection.map(s => {
        return s.id
      })
      var list2 = this.$refs.multipleTable2.selection.map(s => {
        return s.id
      })
      this.checkedPermissions = [...this.checkedPermissions, ...list2]
    },
    onSelect(selection, row) {
      const checked = selection.some(s => s.id === row.id)
      if (row.children && row.children.length > 0) {
        const rows = treeToList(row.children)
        rows.forEach(r => {
          this.$refs.multipleTable.toggleRowSelection(r, checked)
          this.selectApis(checked, r)
        })
      } else {
        this.selectApis(checked, row)
      }

      const parents = getTreeParentsWithSelf(this.permissionTree, row.id)
      parents.forEach(parent => {
        const checked = this.checkedPermissions.includes(parent.id)
        if (!checked) {
          this.$refs.multipleTable.toggleRowSelection(parent, true)
        }
      })

      this.checkedPermissions = this.$refs.multipleTable.selection.map(s => {
        return s.id
      })
      var list2 = this.$refs.multipleTable2.selection.map(s => {
        return s.id
      })
      this.checkedPermissions = [...this.checkedPermissions, ...list2]
    },
    onChange(value, id) {
      if (value) {
        const parents = getTreeParentsWithSelf(this.permissionTree, id)
        parents.forEach(parent => {
          const checked = this.checkedPermissions.includes(parent.id)
          if (!checked) {
            this.$refs.multipleTable.toggleRowSelection(parent, true)
          }
        })

        this.checkedPermissions = this.$refs.multipleTable.selection.map(s => {
          return s.id
        })
        var list2 = this.$refs.multipleTable2.selection.map(s => {
          return s.id
        })
        this.checkedPermissions = [...this.checkedPermissions, ...list2]
      }
    },

    onSelectAll2(selection) {
      const selections = treeToList(selection)
      const rows = treeToList(this.permissionTree2)
      const checked = selections.length === rows.length
      rows.forEach(row => {
        this.$refs.multipleTable2.toggleRowSelection(row, checked)
        this.selectApis(checked, row)
      })

      this.checkedPermissions = this.$refs.multipleTable.selection.map(s => {
        return s.id
      })
      var list2 = this.$refs.multipleTable2.selection.map(s => {
        return s.id
      })
      this.checkedPermissions = [...this.checkedPermissions, ...list2]
    },
    onSelect2(value, row) {
      const checked = value.length > 0
      const index = this.chekedApis.indexOf(row?.id)
      const index2 = this.checkedPermissions.indexOf(row?.id)
      if (checked) {
        if (index === -1) {
          this.chekedApis.push(row?.id)
        }
        if (index2 === -1) {
          this.checkedPermissions.push(row?.id)
        }
      } else {
        if (index > -1) {
          this.chekedApis.splice(index, 1)
        }
        if (index2 > -1) {
          this.checkedPermissions.splice(index2, 1)
        }
      }
    }
  }
}
</script>

<style scoped>
.role-item {
  font-size: 14px;
  cursor: pointer;
  padding: 10px;
}

.role-item.active {
  background: #ebf5ff;
}

.role-item:hover {
  background: #ebf5ff;
}

.clearfix:before,
.clearfix:after {
  display: table;
  content: "";
}
.clearfix:after {
  clear: both;
}

.save ::v-deep [_button] {
  padding: 3px 0px;
}
</style>
